package cn.mw.cmdb.service.impl;

import cn.hutool.extra.spring.SpringUtil;
import cn.mw.cmdb.entity.*;
import cn.mw.cmdb.enums.MonitorModeType;
import cn.mw.cmdb.enums.OperatorTypeDescEnum;
import cn.mw.cmdb.exception.TemplateDescriptionExistException;
import cn.mw.cmdb.exception.TemplateOidExistException;
import cn.mw.cmdb.exception.WarnTitleException;
import cn.mw.cmdb.mongoMapper.ModelMacroMapper;
import cn.mw.cmdb.mongoMapper.ModelTemplateMapper;
import cn.mw.cmdb.param.*;
import cn.mw.cmdb.processor.MonitorParamContext;
import cn.mw.cmdb.processor.MonitorProcessor;
import cn.mw.cmdb.service.ModelTemplateService;
import cn.mw.cmdb.service.MwMonitorProcessorConvert;
import cn.mw.cmdb.util.CMDBTool;
import cn.mw.cmdb.util.ExcelUtils;
import cn.mw.components.mongodb.entity.SearchParam;
import cn.mw.components.mongodb.tool.CriteriaWrapper;
import cn.mw.log.client.LogClientSimple;
import cn.mw.log.enums.BusinessLogType;
import cn.mw.log.enums.LogLevel;
import cn.mw.main.api.common.ZabbixDubboService;
import cn.mw.microMonitorCommon.api.common.MwTPServerService;
import cn.mw.microMonitorCommon.constant.Constants;
import cn.mw.microMonitorCommon.constants.ZabbixApiConstants;
import cn.mw.microMonitorCommon.entity.common.MwTPServerTable;
import cn.mw.microMonitorCommon.entity.zabbix.MWZabbixAPIResult;
import cn.mw.microMonitorCommon.enums.ServerTypeEnum;
import cn.mw.microMonitorCommon.security.dto.MwUser;
import cn.mw.microMonitorCommon.security.utils.SecurityUtils;
import cn.mw.microMonitorCommon.util.DateUtils;
import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelWriter;
import com.alibaba.excel.metadata.Head;
import com.alibaba.excel.metadata.data.WriteCellData;
import com.alibaba.excel.write.metadata.WriteSheet;
import com.alibaba.excel.write.metadata.holder.WriteSheetHolder;
import com.alibaba.excel.write.style.column.AbstractColumnWidthStyleStrategy;
import com.alibaba.fastjson.JSONArray;
import com.google.common.base.Strings;
import com.google.common.collect.Lists;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.poi.ss.usermodel.Cell;
import org.springframework.context.MessageSource;
import org.springframework.context.i18n.LocaleContextHolder;
import org.springframework.data.mongodb.core.BulkOperations;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.data.util.Pair;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.util.*;
import java.util.stream.Collectors;

import static cn.mw.cmdb.enums.PageDescEnum.ModelTemplate;
import static cn.mw.cmdb.processor.zabbix.ZabbixMonitorProcessor.templateKey;
import static cn.mw.cmdb.util.ValConvertUtil.*;

@Slf4j
public class ModelTemplateServiceImpl extends ModelBaseServiceImpl<ModelTemplateInfo, TemplateIdsParam> implements ModelTemplateService {

    private ModelTemplateMapper modelTemplateMapper;
    private CmdbServiceManage cmdbServiceManage;
    //监控服务器上模板id
    private static final String TEMPLATE_ID = "templateid";
    //监控服务器上模板名称
    private static final String NAME = "name";

    private MwTPServerService mwTPServerService;

    private ZabbixDubboService zabbixDubboService;

    private ModelMacroMapper modelMacroMapper;
    private LogClientSimple logClientSimple;

    public ModelTemplateServiceImpl(ModelTemplateMapper modelTemplateMapper, ModelMacroMapper modelMacroMapper, CmdbServiceManage cmdbServiceManage, MwTPServerService mwTPServerService, ZabbixDubboService zabbixDubboService) {
        this.cmdbServiceManage = cmdbServiceManage;
        this.modelTemplateMapper = modelTemplateMapper;
        this.mwTPServerService = mwTPServerService;
        this.zabbixDubboService = zabbixDubboService;
        this.modelMacroMapper = modelMacroMapper;
    }

    public ModelTemplateServiceImpl() {
        this.logClientSimple = SpringUtil.getBean(LogClientSimple.class);

    }

    public static final String ID = "template";

    @Override
    public ModelTemplateInfo genObject() {
        return new ModelTemplateInfo();
    }


    @Override
    Object doAdd(ModelTemplateInfo param) throws Exception {
        //特征信息，规格型号校验
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getTemplateName).is(param.getTemplateName()));
        query.addCriteria(new Criteria(CMDBTool.getFieldName(ModelTemplateInfo::getDescription)).is(param.getDescription()));
        query.addCriteria(new Criteria(CMDBTool.getFieldName(ModelTemplateInfo::getSpecificationId)).is(param.getSpecificationId()));
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        List<ModelTemplateInfo> list = modelTemplateMapper.find(query);
        //特征信息不能重复
        if (CollectionUtils.isNotEmpty(list)) {
            throw new TemplateDescriptionExistException();
        }
        query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getTemplateName).is(param.getTemplateName()));
        query.addCriteria(new Criteria(CMDBTool.getFieldName(ModelTemplateInfo::getSystemObjid)).is(param.getSystemObjid()));
        query.addCriteria(new Criteria(CMDBTool.getFieldName(ModelTemplateInfo::getSpecificationId)).is(param.getSpecificationId()));
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        List<ModelTemplateInfo> list1 = modelTemplateMapper.find(query);
        //系统oid不能重复
        if (CollectionUtils.isNotEmpty(list1)) {
            if(Strings.isNullOrEmpty(param.getSystemObjid())){
                throw new WarnTitleException("template-spec-exist");
            }else{
                throw new TemplateOidExistException();
            }
        }

        MwUser user = SecurityUtils.getUser();
        CMDBTool.initCreateInfo(param);
        param.setStatus(true);
        ModelTemplateInfo insert = modelTemplateMapper.insert(param);
        //更新监控服务器模板数据
        updateTemplateInfobyServer(insert.getId());
        return insert;
    }

    @Override
    boolean doUpdate(ModelTemplateInfo param) throws Exception {
        CMDBTool.initUpdateInfo(param);
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getId).is(param.getId()));
        Update update = CMDBTool.genMongoUpdate(param, null, null);
        CMDBTool.updateFirst(modelTemplateMapper, query, update);
        return true;
    }


    /**
     * 不同条件下的批量更新
     *
     * @param params
     * @throws Exception
     */
    @Override
    public void batchUpdateTemplate(List<ModelTemplateInfo> params) throws Exception {
        List<Pair<Query, Update>> updateList = new ArrayList<>();
        //UNORDERED是异步执行，有错误跳过继续执行；ORDERED时有序执行，遇到错误终止
        BulkOperations operations = modelTemplateMapper.bulkOps(BulkOperations.BulkMode.UNORDERED, ModelTemplateInfo.class);
        for (ModelTemplateInfo data : params) {
            // 添加查询条件
            Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getId).is(data.getId()));
            Update update = new Update();
            // 更新数据
            update.set(CMDBTool.getFieldName(ModelTemplateInfo::getServerTemplates), data.getServerTemplates());
            Pair<Query, Update> updatePair = Pair.of(query, update);
            updateList.add(updatePair);
        }
        operations.updateMulti(updateList);
        operations.execute();
    }


    @Override
    boolean doRemove(ModelTemplateInfo param) throws Exception {

        return false;
    }

    @Override
    Object doBatchAdd(Object params) throws Exception {
        List<ModelTemplateInfo> paramsList = new ArrayList<>();
        if (params != null && params instanceof List) {
            paramsList = (List<ModelTemplateInfo>) params;
            for (ModelTemplateInfo templateInfo : paramsList) {
                CMDBTool.initCreateInfo(templateInfo);
            }
        }
        modelTemplateMapper.insertAll(paramsList);
        updateTemplateInfobyServer(null);
        return true;
    }

    @Override
    boolean doBatchUpdate(Object params) {
        return false;
    }

    /**
     * 设置模板启用状态
     *
     * @param param
     * @return
     * @throws Exception
     */
    @Override
    public boolean updateTempStatus(TemplateIdsParam param) throws Exception {
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getId).in(param.getIds()));
        Update update = new Update();
        update.set(CMDBTool.getFieldName(ModelTemplateInfo::getStatus), param.getStatus());
        modelTemplateMapper.updateMulti(query, update);
        return true;
    }

    /**
     * 模板数据导入
     *
     * @param file
     * @param response
     * @throws Exception
     */
    @Override
    public List<TemplateExcelImportParam> importTempByExcel(MultipartFile file, HttpServletResponse response) throws Exception {
        String fileName = file.getOriginalFilename();
        MwUser user = SecurityUtils.getUser();
        String loginName = user.getUsername();
        List<TemplateExcelImportParam> failList = new ArrayList<>();
        if (null != fileName && (fileName.toLowerCase().endsWith(".xls") || fileName.toLowerCase().endsWith(".xlsx"))) {
            EasyExcel.read(file.getInputStream(), TemplateExcelImportParam.class,
                    new TemplateExcelImportListener(response, fileName, loginName, cmdbServiceManage,failList)).sheet().doRead();
        } else {
            log.error("没有传入正确的excel文件名", file);
        }
        return failList;
    }


    @Override
    ModelTemplateInfo doSelectById(Object id) {
        ModelTemplateInfo info = modelTemplateMapper.findById(id);
        return info;
    }

    public List<ModelTemplateInfo> doSelectByIds(List<String> ids) throws Exception {
        Query query = genQueryByIds(ids);
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        List<ModelTemplateInfo> list = modelTemplateMapper.find(query);
        return list;
    }

    @Override
    List<ModelTemplateInfo> doSelectList(Object param) throws Exception {
        TemplateSearchParam searchParam = (TemplateSearchParam) param;
        searchParam.convert();
        Criteria criteria = genCriteria(searchParam);
        if(Strings.isNullOrEmpty(searchParam.getSortName())){
            searchParam.setSortName(CMDBTool.getFieldName(ModelTemplateInfo::getCreateTime) );
            searchParam.setSortOrder("DESC");
        }
        long time1 = System.currentTimeMillis();
        List<ModelTemplateInfo> templateInfos = CMDBTool.aggregateAuthorizedList(ModelTemplateInfo.class, modelTemplateMapper, criteria, searchParam);
        long time2 = System.currentTimeMillis();
        log.info("获取模板list::aggregateAuthorizedList:"+(time2-time1)+"ms");
        for (ModelTemplateInfo modelTemplateInfo : templateInfos) {
            modelTemplateInfo.getMonitorMode();
            modelTemplateInfo.setMonitorModeName(MonitorModeType.getMonitorName(intValueConvert(modelTemplateInfo.getMonitorMode())));
        }
        return templateInfos;
    }

    private void setAdditionalInfo(List<ModelTemplateInfo> list) throws Exception {
        //获取所有模型信息
        CustomModelServiceImpl modelService = (CustomModelServiceImpl) cmdbServiceManage.getModelService(CustomModelServiceImpl.ID);
        List<ModelInfo> modelInfos = modelService.findAllList();
        Map<String, String> modelMap = modelInfos.stream().collect(Collectors.toMap(s -> s.getId(), s -> s.getModelName()));
        //获取所有分组信息
        ModelGroupServiceImpl groupService = (ModelGroupServiceImpl) cmdbServiceManage.getModelService(ModelGroupServiceImpl.ID);
        List<ModelGroupInfo> groupInfos = groupService.doSelectList(new SearchParam());
        Map<String, String> groupMap = groupInfos.stream().collect(Collectors.toMap(s -> s.getId(), s -> s.getName()));
        //获取所有厂商信息
        ModelVendorServiceImpl vendorService = (ModelVendorServiceImpl) cmdbServiceManage.getModelService(ModelVendorServiceImpl.ID);
        List<ModelVendorInfo> vendorInfoList = vendorService.doSelectList(new VendorSearchParam());
        Map<String, String> vendorMap = vendorInfoList.stream().filter(s->s.getVendorCN()!=null).collect(Collectors.toMap(s -> s.getId(), s -> s.getVendorCN()));
        //获取所有规格信号信息
        ModelSpecificationServiceImpl specService = (ModelSpecificationServiceImpl) cmdbServiceManage.getModelService(ModelSpecificationServiceImpl.ID);
        List<ModelSpecificationInfo> specInfoList = specService.doSelectList(new SpecificationSearchParam());
        Map<String, String> specMap = specInfoList.stream().collect(Collectors.toMap(s -> s.getId(), s -> s.getSpecification()));
        for (ModelTemplateInfo info : list) {
            if (modelMap != null && modelMap.containsKey(info.getModelId())) {
                info.setModelName(modelMap.get(info.getModelId()));
            }
            if (groupMap != null && groupMap.containsKey(info.getModelGroupId())) {
                info.setModelGroupName(groupMap.get(info.getModelGroupId()));
            }
            if (vendorMap != null && vendorMap.containsKey(info.getBrandId())) {
                info.setBrand(vendorMap.get(info.getBrandId()));
            }
            if (specMap != null && specMap.containsKey(info.getSpecificationId())) {
                info.setSpecification(specMap.get(info.getSpecificationId()));
            }
            info.setMonitorModeName(MonitorModeType.getMonitorName(info.getMonitorMode()));
        }
    }

    List<ModelTemplateInfo> getAllList() throws Exception {
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        List<ModelTemplateInfo> list = modelTemplateMapper.find(query);
        return list;
    }

    List<ModelTemplateInfo> getListByQuery(Query query) throws Exception {
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        List<ModelTemplateInfo> list = modelTemplateMapper.find(query);
        setAdditionalInfo(list);
        return list;
    }


    @Override
    boolean doBatchRemove(TemplateIdsParam params) throws Exception {
        CMDBTool.remove(modelTemplateMapper, params.getIds(), ModelTemplateInfo.class, true);
        return true;
    }

    @Override
    public List<TemplateZabbixParam> getTemplateListByZabbix() {
        List<MwTPServerTable> allMwTpServer = mwTPServerService.getAllMwTpServer(ServerTypeEnum.Zabbix.getCode(), false);
        log.info("getTemplateListByZabbix::allMwTpServer" + allMwTpServer);
        MwTPServerTable serverTable = new MwTPServerTable();
        boolean isMainServer = false;
        if (CollectionUtils.isNotEmpty(allMwTpServer)) {
            for (MwTPServerTable table : allMwTpServer) {
                //是否主监控服务器
                if (booleanValueConvert(table.getMainServer())) {
                    serverTable = table;
                    isMainServer = true;
                }
            }
            //否则随机选择一个
            if (!isMainServer) {
                serverTable = allMwTpServer.get(0);
            }
        }
        log.info("serverTable.getId()" + serverTable.getId());
        MWZabbixAPIResult mwZabbixAPIResult = zabbixDubboService.getZabbixApiResult(ZabbixApiConstants.TEMPLATE_GET, serverTable.getId(), null);
        log.info("getServerTemplateInfo::" + mwZabbixAPIResult.getData());
        List<TemplateZabbixParam> list = new ArrayList<>();
        if (mwZabbixAPIResult != null && mwZabbixAPIResult.getCode() == 0) {
            list = JSONArray.parseArray(strValueConvert(mwZabbixAPIResult.getData()), TemplateZabbixParam.class);
        }
        return list;
    }

    @Override
    public boolean syncTemplateInfo() throws Exception {
        Boolean boolTemp = updateTemplateInfobyServer(null);
        ModelGroupServiceImpl modelGroupService = (ModelGroupServiceImpl) cmdbServiceManage.getModelService(ModelGroupServiceImpl.ID);
        modelGroupService.syncGroupInfoFromMoniterServer();
//        Boolean boolGroup = updateModelGroupInfo();
//        Boolean isSuccess = boolTemp && boolGroup;
        return boolTemp;
    }

    private Boolean updateTemplateInfobyServer(String id) throws Exception {
        List<ModelTemplateInfo> templateNamesDtos = new ArrayList<>();
        String tempName = null;
        if (Strings.isNullOrEmpty(id)) {
            templateNamesDtos = getAllList();
        } else {
            ModelTemplateInfo templateNamesDto = selectById(id);
            tempName = templateNamesDto.getTemplateName();
            templateNamesDtos.add(templateNamesDto);
        }
        List<MwTPServerTable> allMwTpServer = mwTPServerService.getAllMwTpServer(ServerTypeEnum.Zabbix.getCode(), false);

        Map<String, List<TemplateZabbixParam>> templateZabbixMap = new HashMap<>();
        List<TemplateZabbixParam> templateZabbixList = new ArrayList<>();
        for (MwTPServerTable mwTPServerTable : allMwTpServer) {
            //获取所有的模板数据信息
            MWZabbixAPIResult mwZabbixAPIResult = zabbixDubboService.getZabbixApiResult(ZabbixApiConstants.TEMPLATE_GET, mwTPServerTable.getId(), tempName, true);
            if (mwZabbixAPIResult != null && mwZabbixAPIResult.getCode() == 0) {
                List<TemplateZabbixParam> templateList = JSONArray.parseArray(strValueConvert(mwZabbixAPIResult.getData()), TemplateZabbixParam.class);
                for (TemplateZabbixParam param : templateList) {
                    param.setServerId(strValueConvert(mwTPServerTable.getId()));
                    templateZabbixList.add(param);
                }
            }
        }
        //以模板名称为key，groupBy分组
        templateZabbixMap = templateZabbixList.stream().filter(s -> s.getName() != null).collect(Collectors.groupingBy(s -> s.getName()));


        for (ModelTemplateInfo templateNamesDto : templateNamesDtos) {
            String name = templateNamesDto.getTemplateName();
            if (templateZabbixMap != null && templateZabbixMap.containsKey(name)) {
                List<TemplateZabbixParam> templateZabbixParams = templateZabbixMap.get(name);
                if (CollectionUtils.isNotEmpty(templateZabbixParams)) {
                    List<ServerTemplateInfo> serverTemplates = new ArrayList<>();
                    for (TemplateZabbixParam param : templateZabbixParams) {
                        String templateName = param.getName();
                        ServerTemplateInfo serverTemplateInfo = new ServerTemplateInfo();
                        if (templateNamesDto.getTemplateName().equals(templateName)) {
                            String templateid = param.getTemplateid();
                            serverTemplateInfo.setServerId(strValueConvert(param.getServerId()));
                            serverTemplateInfo.setServerTemplateId(templateid);
                            serverTemplates.add(serverTemplateInfo);
                        }
                    }
                    templateNamesDto.setServerTemplates(serverTemplates);
                }
            }
        }

        List<String> ids = new ArrayList<>();
        for (ModelTemplateInfo templateNamesDto : templateNamesDtos) {
            if (Strings.isNullOrEmpty(templateNamesDto.getTemplateName())) {
                ids.add(templateNamesDto.getId());
            }
        }
        if (CollectionUtils.isNotEmpty(ids)) {
            TemplateIdsParam params = new TemplateIdsParam();
            params.setIds(ids);
            doBatchRemove(params);
        }
        //批量更新模板表
        List<List<ModelTemplateInfo>> listGroups = null;
        if (templateNamesDtos.size() > 0) {
            listGroups = Lists.partition(templateNamesDtos, 1000);
            for (List<ModelTemplateInfo> listParam : listGroups) {
                batchUpdateTemplate(listParam);
            }
        }
        return true;
    }

    private Boolean updateModelGroupInfo() {
        return true;
    }

    @Override
    public int exportTempByExcel(TemplateSearchParam searchParam, HttpServletRequest request, HttpServletResponse response) throws Exception {
        ExcelWriter excelWriter = null;
        int num = 0;
        try {
            List<String> includeColumnFiledNames = new ArrayList<>();
            if (CollectionUtils.isEmpty(searchParam.getHeader())) {
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getBrand));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getSpecification));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getMonitorModeName));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getSystemObjid));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getTemplateName));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getModelGroupName));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getModelName));
                includeColumnFiledNames.add(CMDBTool.getFieldName(TemplateExcelImportParam::getDescription));
            } else {
                includeColumnFiledNames = searchParam.getHeader();
            }
            excelWriter = ExcelUtils.getExcelWriter("exportModelTemplate", response, TemplateExcelImportParam.class);
            WriteSheet sheet = EasyExcel.writerSheet(0, "sheet" + 0)
                    .includeColumnFiledNames(includeColumnFiledNames)
                    .registerWriteHandler(ExcelUtils.writeTemplateStyle())
                    .registerWriteHandler(new TemplateColumWithStyle())
                    .build();
            List<ModelTemplateInfo> modelTemplateInfoList;
            if (searchParam.isExportTemp()) {//导出下载模板时，不需要数据，直接传空数据
                modelTemplateInfoList = new ArrayList<>();
            } else {
                searchParam.setOperation(SearchParam.keyword);
                searchParam.setKeywordValue("");
                modelTemplateInfoList = doSelectList(searchParam);
            }
            excelWriter.write(modelTemplateInfoList, sheet);
            log.info("导出成功");
            if(CollectionUtils.isNotEmpty(modelTemplateInfoList)){
                num = modelTemplateInfoList.size();
            }
        } catch (IOException e) {
            log.error("导出失败{}", e);
        } finally {
            if (null != excelWriter) {
                excelWriter.finish();
            }
        }
        return num;
    }

    /**
     * 获取模板描述信息
     *
     * @param param
     * @throws Exception
     */
    public String getTempDescrInfo(TemplateSearchParam param) throws Exception {
        String descr = "";
        //取所有启用状态的模板数据
        param.convert();
        Criteria criteria = genCriteria(param);
        List<ModelTemplateInfo> templateInfos = CMDBTool.selectListByAggregate(ModelTemplateInfo.class, modelTemplateMapper, criteria);
        if (CollectionUtils.isNotEmpty(templateInfos)) {
            descr = templateInfos.get(0).getDescription();
        }
        return descr;
    }


    /**
     * 获取模板信息和监控方式
     *
     * @param param
     * @throws Exception
     */
    @Override
    public List<QueryModelTemplateParam> selectTempInfoAndMonitorMode(ModelTemplateInfo param) throws Exception {
        //取所有启用状态的模板数据
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getStatus).is(true));
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        if (!Strings.isNullOrEmpty(param.getId())) {
            query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getId).is(param.getId()));
        }
        List<ModelTemplateInfo> allTempList = modelTemplateMapper.find(query);
        List<QueryModelTemplateParam> templateNames = new ArrayList<>();
        for (ModelTemplateInfo info : allTempList) {
            String templateName = info.getTemplateName();
            if (info.getMonitorMode() != null) {
                QueryModelTemplateParam queryModelTemplateParam = new QueryModelTemplateParam();
                queryModelTemplateParam.setTemplateName(templateName);
//                queryModelTemplateParam.setMonitorMode(info.getMonitorMode());
                templateNames.add(queryModelTemplateParam);
            }
        }
        List<QueryModelTemplateParam> templateParamList = templateNames.stream().filter(data -> data.getTemplateName() != null).collect(Collectors.collectingAndThen(Collectors.toCollection(() -> new TreeSet<>(Comparator.comparing(QueryModelTemplateParam::getTemplateName))), ArrayList::new));
        List<QueryModelTemplateParam> collect = templateParamList.stream().sorted(Comparator.comparing(QueryModelTemplateParam::getTemplateName)).collect(Collectors.toList());
        return collect;
    }

    /**
     * 根据模板名称查询监控方式
     * @param param
     * @return
     * @throws Exception
     */
    public List<MwModelLabelValueParam> selectMonitorModeByTemplateName(QueryModelTemplateParam param) throws Exception {
        //取所有启用状态的模板数据
        Query query = new Query(CriteriaWrapper.where(ModelTemplateInfo::getStatus).is(true));
        query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getDelFlag).is(false));
        if (!Strings.isNullOrEmpty(param.getTemplateName())) {
            query.addCriteria(CriteriaWrapper.where(ModelTemplateInfo::getTemplateName).is(param.getTemplateName()));
        }
        List<ModelTemplateInfo> allTempList = modelTemplateMapper.find(query);
        List<MwModelLabelValueParam> list = new ArrayList<>();
        if(CollectionUtils.isNotEmpty(allTempList)){
            Set<Integer> monitorModeList = allTempList.stream().filter(s -> s.getMonitorMode() != null).map(s -> s.getMonitorMode()).collect(Collectors.toSet());
            for(Integer monitorModel : monitorModeList){
                MwModelLabelValueParam labelValueParam = new MwModelLabelValueParam();
                labelValueParam.setLabel(MonitorModeType.getMonitorName(monitorModel));
                labelValueParam.setValue(monitorModel);
                list.add(labelValueParam);
            }
        }
        return list;
    }


    private class TemplateColumWithStyle extends AbstractColumnWidthStyleStrategy {
        @Override
        protected void setColumnWidth(WriteSheetHolder writeSheetHolder, List<WriteCellData<?>> cellDataList, Cell cell, Head head, Integer relativeRowIndex, Boolean isHead) {
            if (isHead) {
                writeSheetHolder.getSheet().setColumnWidth(cell.getColumnIndex(), 6000);
            }
        }
    }

    public List<MwMacros> getMacInfoByTemplate(TemplateSearchParam searchParam) throws Exception {
        List<MacrosInfo> macros = new ArrayList<>();
        Map<Integer, String> m = new HashMap();
        List<ModelTemplateInfo> templateInfos = doSelectList(searchParam);

        Set<ServerTemplateInfo> serverTemplateSet = new HashSet();
        for (ModelTemplateInfo info : templateInfos) {
            if (CollectionUtils.isNotEmpty(info.getServerTemplates())) {
                serverTemplateSet.addAll(info.getServerTemplates());
            }
        }
        for (ServerTemplateInfo info : serverTemplateSet) {
            m.put(intValueConvert(info.getServerId()), info.getServerTemplateId());
        }
        List<MacrosInfo> macrosInfo = modelMacroMapper.findAll();
        List<MwMacros> macrosData = new ArrayList<>();
        MwMonitorProcessorConvert processorConvert = new MwMonitorProcessorConvert(cmdbServiceManage, zabbixDubboService);
        MonitorParamContext contextParam = processorConvert.getContextParam(macrosInfo, null);
        List<MwTPServerTable> allMwTpServer = mwTPServerService.getAllMwTpServer(ServerTypeEnum.Zabbix.getCode(), false);
        for (MwTPServerTable mwTPServerTable : allMwTpServer) {
            MonitorProcessor processor = MonitorProcessor.build(mwTPServerTable, null);
            String templateId = m.get(mwTPServerTable.getId());
            if (!Strings.isNullOrEmpty(templateId)) {
                Map mapParam = new HashMap();
                mapParam.put(templateKey, templateId);
                contextParam.setMapParam(mapParam);
                macrosData = processor.getMacrosByTemplateId(contextParam);
            }
            if (CollectionUtils.isNotEmpty(macrosData)) {
                //多个zabbix服务器，只要有一个有值，就直接获取，剩余的直接跳出。
                break;
            }
        }
        return macrosData;
    }


    /**
     * 新增异常日志记录
     *
     * @param param
     */
    public void addRecordMethod(Object param) {
        String name = "";
        if (param != null && param instanceof ModelTemplateInfo) {
            ModelTemplateInfo info = (ModelTemplateInfo) param;
            name = info.getTemplateName();
        }
        String nickName = SecurityUtils.getUser().getNickName();
        MessageSource messageSource = SpringUtil.getBean(MessageSource.class);
        logClientSimple.addBusinessLog(LogLevel.INFO.getId(), BusinessLogType.CMDB_MANAGE.getId(),
                messageSource.getMessage("mwCmdb-operation-log", new Object[]{nickName, DateUtils.now()
                        , BusinessLogType.CMDB_MANAGE.getCnName(), OperatorTypeDescEnum.add.getCname() + ModelTemplate.getDesc(),
                        OperatorTypeDescEnum.add.getCname() + name, Constants.OperationStatus.FAILED}, LocaleContextHolder.getLocale()));
    }

    /**
     * 修改异常日志记录
     *
     * @param param
     */
    public void updateRecordMethod(Object param) {
        String name = "";
        if (param != null && param instanceof ModelTemplateInfo) {
            ModelTemplateInfo info = (ModelTemplateInfo) param;
            name = info.getTemplateName();
        }
        String nickName = SecurityUtils.getUser().getNickName();
        MessageSource messageSource = SpringUtil.getBean(MessageSource.class);
        logClientSimple.addBusinessLog(LogLevel.INFO.getId(), BusinessLogType.CMDB_MANAGE.getId(),
                messageSource.getMessage("mwCmdb-operation-log", new Object[]{nickName, DateUtils.now()
                        , BusinessLogType.CMDB_MANAGE.getCnName(), OperatorTypeDescEnum.update.getCname() + ModelTemplate.getDesc(),
                        OperatorTypeDescEnum.update.getCname() + name, Constants.OperationStatus.FAILED}, LocaleContextHolder.getLocale()));
    }

    /**
     * 删除异常日志记录
     *
     * @param param
     */
    private void removeRecordMethod(Object param) {

        }

    /**
     * 批量新增异常日志记录
     *
     * @param params
     */
    private void batchAddRecordMethod(Object params) {
        String name = "";
        List<ModelTemplateInfo> paramsList = new ArrayList<>();
        if (params != null && params instanceof List) {
            paramsList = (List<ModelTemplateInfo>) params;
            List<String> collect = paramsList.stream().map(s -> s.getTemplateName()).collect(Collectors.toList());
            name = String.join(",", collect);
        }
        String nickName = SecurityUtils.getUser().getNickName();
        MessageSource messageSource = SpringUtil.getBean(MessageSource.class);
        logClientSimple.addBusinessLog(LogLevel.INFO.getId(), BusinessLogType.CMDB_MANAGE.getId(),
                messageSource.getMessage("mwCmdb-operation-log", new Object[]{nickName, DateUtils.now()
                        , BusinessLogType.CMDB_MANAGE.getCnName(), OperatorTypeDescEnum.batchAdd.getCname() + ModelTemplate.getDesc(),
                        OperatorTypeDescEnum.batchAdd.getCname() + name, Constants.OperationStatus.FAILED}, LocaleContextHolder.getLocale()));
    }

    /**
     * 批量修改异常日志记录
     *
     * @param param
     */
    private void batchUpdateRecordMethod(Object param) {

    }

    /**
     * 批量删除异常日志记录
     *
     * @param params
     */
    private void batchRemoveRecordMethod(Object params) throws Exception {
        String name = "";
        if (params != null && params instanceof TemplateIdsParam) {
            List<String> ids = ((TemplateIdsParam) params).getIds();
            List<ModelTemplateInfo> templateInfos = doSelectByIds(ids);
            List<String> collect = templateInfos.stream().map(s -> s.getTemplateName()).collect(Collectors.toList());
            name = String.join(",", collect);
        }
        String nickName = SecurityUtils.getUser().getNickName();
        MessageSource messageSource = SpringUtil.getBean(MessageSource.class);
        logClientSimple.addBusinessLog(LogLevel.INFO.getId(), BusinessLogType.CMDB_MANAGE.getId(),
                messageSource.getMessage("mwCmdb-operation-log", new Object[]{nickName, DateUtils.now()
                        , BusinessLogType.CMDB_MANAGE.getCnName(), OperatorTypeDescEnum.batchRemove.getCname() + ModelTemplate.getDesc(),
                        OperatorTypeDescEnum.batchRemove.getCname() + name, Constants.OperationStatus.FAILED}, LocaleContextHolder.getLocale()));

    }


}
